/*
 * Copyright (c) 2025 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.uniinputsample;

import android.content.Context;

import com.facebook.flipper.android.AndroidFlipperClient;
import com.facebook.flipper.android.utils.FlipperUtils;
import com.facebook.flipper.core.FlipperClient;
import com.facebook.flipper.plugins.crashreporter.CrashReporterPlugin;
import com.facebook.flipper.plugins.databases.DatabasesFlipperPlugin;
import com.facebook.flipper.plugins.fresco.FrescoFlipperPlugin;
import com.facebook.flipper.plugins.inspector.DescriptorMapping;
import com.facebook.flipper.plugins.inspector.InspectorFlipperPlugin;
import com.facebook.flipper.plugins.network.FlipperOkhttpInterceptor;
import com.facebook.flipper.plugins.network.NetworkFlipperPlugin;
import com.facebook.flipper.plugins.sharedpreferences.SharedPreferencesFlipperPlugin;
import com.facebook.react.ReactInstanceEventListener;
import com.facebook.react.ReactInstanceManager;
import com.facebook.react.bridge.ReactContext;
import com.facebook.react.modules.network.NetworkingModule;

import okhttp3.OkHttpClient;

/**
 * 该类负责在您的本应用程序中加载Flipper。由于我们不希望加载Flipper,因此为空。
 *
 * @since 2025-07-22
 */
public class ReactNativeFlipper {
    /**
     * 初始化Flipper客户端。
     *
     * @param context              应用程序上下文
     * @param reactInstanceManager React实例管理器
     */
    public static void initializeFlipper(Context context, ReactInstanceManager reactInstanceManager) {
        if (FlipperUtils.shouldEnableFlipper(context)) {
            final FlipperClient client = AndroidFlipperClient.getInstance(context);
            initializeCorePlugins(client, context);
            initializeNetworkPlugin(client);
            initializeFrescoPlugin(client, reactInstanceManager);
            client.start();
        }
    }

    private static void initializeCorePlugins(FlipperClient client, Context context) {
        client.addPlugin(new InspectorFlipperPlugin(context, DescriptorMapping.withDefaults()));
        client.addPlugin(new DatabasesFlipperPlugin(context));
        client.addPlugin(new SharedPreferencesFlipperPlugin(context));
        client.addPlugin(CrashReporterPlugin.getInstance());
    }

    private static void initializeNetworkPlugin(FlipperClient client) {
        NetworkFlipperPlugin networkFlipperPlugin = new NetworkFlipperPlugin();
        NetworkingModule.setCustomClientBuilder(
                new NetworkingModule.CustomClientBuilder() {
                    @Override
                    public void apply(OkHttpClient.Builder builder) {
                        builder.addNetworkInterceptor(new FlipperOkhttpInterceptor(networkFlipperPlugin));
                    }
                });
        client.addPlugin(networkFlipperPlugin);
    }

    private static void initializeFrescoPlugin(FlipperClient client, ReactInstanceManager reactInstanceManager) {
        // Fresco Plugin needs to ensure that ImagePipelineFactory is initialized
        // Hence we run if after all native modules have been initialized
        ReactContext reactContext = reactInstanceManager.getCurrentReactContext();
        if (reactContext == null) {
            reactInstanceManager.addReactInstanceEventListener(new ReactInstanceEventListener() {
                @Override
                public void onReactContextInitialized(ReactContext reactContext) {
                    reactInstanceManager.removeReactInstanceEventListener(this);
                    addFrescoFlipperPlugin(client, reactContext);
                }
            });
        } else {
            client.addPlugin(new FrescoFlipperPlugin());
        }
    }

    private static void addFrescoFlipperPlugin(FlipperClient client, ReactContext reactContext) {
        reactContext.runOnNativeModulesQueueThread(
                new Runnable() {
                    @Override
                    public void run() {
                        client.addPlugin(new FrescoFlipperPlugin());
                    }
                });
    }
}
